
import 'dart:ffi' as ffi;
import 'package:ffi/ffi.dart';
import 'package:tencent_rtc/bindings/ffi_bindings.dart' as native;
import 'package:tencent_rtc/bindings/trtc_cloud_struct.dart';
import 'package:tencent_rtc/bindings/load_dynamic_lib.dart';

import 'package:tencent_rtc/tx_audio_effect_manager.dart';


class TXAudioEffectManagerNative {
  late native.FFIBindings _audioEffectFFIBindings;
  late tx_audio_effect_manager _audioEffectNativePointer;

  TXAudioEffectManagerNative(tx_device_manager audioEffectNativePointer) {
    _audioEffectNativePointer = audioEffectNativePointer;
    _audioEffectFFIBindings = native.FFIBindings(LoadDynamicLib().loadTRTCSDK());
  }

  tx_audio_effect_manager getNativePointer() {
    return _audioEffectNativePointer;
  }


  void enableVoiceEarMonitor(bool enable) {
    _audioEffectFFIBindings.enable_voice_ear_monitor(_audioEffectNativePointer, enable);
  }

  int getMusicCurrentPosInMS(int id) {
    return _audioEffectFFIBindings.get_current_pos_in_ms(_audioEffectNativePointer, id);
  }

  int getMusicDurationInMS(String path) {
    ffi.Pointer<ffi.Char> pathPointer = path.toNativeUtf8().cast<ffi.Char>();

    int result =  _audioEffectFFIBindings.get_music_duration_in_ms(_audioEffectNativePointer, pathPointer);

    calloc.free(pathPointer);
    return result;
  }

  int getMusicTrackCount(int id) {
    return _audioEffectFFIBindings.get_music_track_count(_audioEffectNativePointer, id);
  }

  void pausePlayMusic(int id) {
    _audioEffectFFIBindings.pause_play_music(_audioEffectNativePointer, id);
  }

  void preloadMusic(AudioMusicParam musicParam) {
    ffi.Pointer<tx_audio_music_param_t> musicParamPointer = tx_audio_music_param_t.fromParams(musicParam);

    _audioEffectFFIBindings.preload_music(_audioEffectNativePointer, musicParamPointer.ref);

    calloc.free(musicParamPointer);
  }

  void resumePlayMusic(int id) {
    _audioEffectFFIBindings.resume_play_music(_audioEffectNativePointer, id);
  }

  void seekMusicToPosInTime(int id, int pts) {
    _audioEffectFFIBindings.seek_music_to_pos_in_time(_audioEffectNativePointer, id, pts);
  }

  void setAllMusicVolume(int volume) {
    _audioEffectFFIBindings.set_all_music_volume(_audioEffectNativePointer, volume);
  }

  void setMusicPitch(int id, double pitch) {
    _audioEffectFFIBindings.set_music_pitch(_audioEffectNativePointer, id, pitch);
  }

  void setMusicPlayoutVolume(int id, int volume) {
    _audioEffectFFIBindings.set_music_playout_volume(_audioEffectNativePointer, id, volume);
  }

  void setMusicPublishVolume(int id, int volume) {
    _audioEffectFFIBindings.set_music_publish_volume(_audioEffectNativePointer, id, volume);
  }

  void setMusicScratchSpeedRate(int id, double scratchSpeedRate) {
    _audioEffectFFIBindings.set_music_scratch_speed_rate(_audioEffectNativePointer, id, scratchSpeedRate);
  }

  void setMusicSpeedRate(int id, double rate) {
    _audioEffectFFIBindings.set_music_speed_rate(_audioEffectNativePointer, id, rate);
  }

  void setMusicTrack(int id, int trackIndex) {
    _audioEffectFFIBindings.set_music_track(_audioEffectNativePointer, id, trackIndex);
  }

  void setVoiceCaptureVolume(int volume) {
    _audioEffectFFIBindings.set_voice_capture_volume(_audioEffectNativePointer, volume);
  }

  void setVoiceChangerType(TXVoiceChangerType type) {
    _audioEffectFFIBindings.set_voice_changer_type(_audioEffectNativePointer, type.value());
  }

  void setVoiceEarMonitorVolume(int volume) {
    _audioEffectFFIBindings.set_voice_ear_monitor_volume(_audioEffectNativePointer, volume);
  }

  void setVoicePitch(double pitch) {
    _audioEffectFFIBindings.set_voice_pitch(_audioEffectNativePointer, pitch);
  }

  void setVoiceReverbType(TXVoiceReverbType type) {
    _audioEffectFFIBindings.set_voice_reverb_type(_audioEffectNativePointer, type.value());
  }

  void startPlayMusic(AudioMusicParam musicParam) {
    ffi.Pointer<tx_audio_music_param_t> musicParamPointer = tx_audio_music_param_t.fromParams(musicParam);

    _audioEffectFFIBindings.start_play_music(_audioEffectNativePointer, musicParamPointer.ref);

    calloc.free(musicParamPointer);
  }

  void stopPlayMusic(int id) {
    _audioEffectFFIBindings.stop_play_music(_audioEffectNativePointer, id);
  }
}